package com.alibaba.cloud.interfaces.web;

import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import com.alibaba.cloud.domain.dto.EmailInfoDto;
import com.alibaba.cloud.domain.dto.PhoneMessageDto;
import com.alibaba.cloud.application.mapping.EmailMessageMapping;
import com.alibaba.cloud.application.mapping.PhoneMessageMapping;
import com.alibaba.cloud.domain.EmailMessage;
import com.alibaba.cloud.domain.MessageEvent;
import com.alibaba.cloud.domain.PhoneMessage;
import com.alibaba.cloud.utils.ResultVo;
import com.lmax.disruptor.RingBuffer;

import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;

/***
 * @description: 消息发送
 * @author: zhb1316783262@163.com
 * @date: 2022/6/25 15:27
 */
@RestController
@RequestMapping("/message")
@RequiredArgsConstructor
@Slf4j
public class MessageController {
    private final RingBuffer<MessageEvent> ringBuffer;

    @PostMapping("sendEmail")
    public ResultVo<String> sendEmail(@RequestBody EmailInfoDto emailInfoDto) {
        EmailMessage emailMessage = EmailMessageMapping.INSTANCE.dtoToPO(emailInfoDto);
        long sequence = ringBuffer.next();
        try {
            //给Event填充数据
            MessageEvent event = ringBuffer.get(sequence);
            event.setBaseMessage(emailMessage);
            log.info("往消息队列中添加消息：{}", event);
        } catch (Exception e) {
            log.error("failed to add event to messageModelRingBuffer for : e = {},{}", e, e.getMessage());
        } finally {
            //发布Event，激活观察者去消费，将sequence传递给改消费者
            //注意最后的publish方法必须放在finally中以确保必须得到调用；如果某个请求的sequence未被提交将会堵塞后续的发布操作或者其他的producer
            ringBuffer.publish(sequence);
        }
        return ResultVo.success("发送成功");
    }

    @PostMapping("sendPhone")
    public ResultVo<String> sendPhone(@RequestBody PhoneMessageDto phoneMessageDto) {
        PhoneMessage phoneMessage = PhoneMessageMapping.INSTANCE.dtoToPO(phoneMessageDto);
        long sequence = ringBuffer.next();
        try {
            //给Event填充数据
            MessageEvent event = ringBuffer.get(sequence);
            event.setBaseMessage(phoneMessage);
            log.info("往消息队列中添加消息：{}", event);
        } catch (Exception e) {
            log.error("failed to add event to messageModelRingBuffer for : e = {},{}", e, e.getMessage());
        } finally {
            //发布Event，激活观察者去消费，将sequence传递给改消费者
            //注意最后的publish方法必须放在finally中以确保必须得到调用；如果某个请求的sequence未被提交将会堵塞后续的发布操作或者其他的producer
            ringBuffer.publish(sequence);
        }
        return ResultVo.success("发送成功");
    }


}
